//
//  NSMutableArray+AviodCrash.m
//  LzlPictureBrower
//
//  Created by luozhilin on 2018/6/5.
//  Copyright © 2018年 luozhilin. All rights reserved.
//

#import "NSMutableArray+AviodCrash.h"
#import "YYAvoidCrash.h"

@implementation NSMutableArray (AviodCrash)

+ (void)avoidCrashExchangeMethod {
    
    static dispatch_once_t onceToken;
    dispatch_once(&onceToken, ^{
        
        Class arrayMClass = NSClassFromString(@"__NSArrayM");
        
        
        //objectAtIndex:
        [YYAvoidCrash exchangeInstanceMethod:arrayMClass originalMethod:@selector(objectAtIndex:) newMethod:@selector(yy_avoidCrashObjectAtIndex:)];
        
        //objectAtIndexedSubscript
        if (AvoidCrashVersion(11.0)) {
            [YYAvoidCrash exchangeInstanceMethod:arrayMClass originalMethod:@selector(objectAtIndexedSubscript:) newMethod:@selector(yy_avoidCrashObjectAtIndexedSubscript:)];
        }

        //setObject:atIndexedSubscript:
        [YYAvoidCrash exchangeInstanceMethod:arrayMClass originalMethod:@selector(setObject:atIndexedSubscript:) newMethod:@selector(yy_avoidCrashSetObject:atIndexedSubscript:)];

        //removeObjectAtIndex:
        [YYAvoidCrash exchangeInstanceMethod:arrayMClass originalMethod:@selector(removeObjectAtIndex:) newMethod:@selector(yy_avoidCrashRemoveObjectAtIndex:)];
        
        //insertObject:atIndex:
        [YYAvoidCrash exchangeInstanceMethod:arrayMClass originalMethod:@selector(insertObject:atIndex:) newMethod:@selector(yy_avoidCrashInsertObject:atIndex:)];
        
        //getObjects:range:
        [YYAvoidCrash exchangeInstanceMethod:arrayMClass originalMethod:@selector(getObjects:range:) newMethod:@selector(yy_avoidCrashGetObjects:range:)];
    });
    
    
    
}


//=================================================================
//                    array set object at index
//=================================================================
#pragma mark - get object from array


- (void)yy_avoidCrashSetObject:(id)obj atIndexedSubscript:(NSUInteger)idx {
    
    @try {
        [self yy_avoidCrashSetObject:obj atIndexedSubscript:idx];
    }
    @catch (NSException *exception) {
        [YYAvoidCrash errorMessageWithException:exception defaultToDo:AvoidCrashDefaultIgnore];
    }
    @finally {
        
    }
}

//                    removeObjectAtIndex:
//=================================================================
#pragma mark - removeObjectAtIndex:

- (void)yy_avoidCrashRemoveObjectAtIndex:(NSUInteger)index {
    @try {
        [self yy_avoidCrashRemoveObjectAtIndex:index];
    }
    @catch (NSException *exception) {
        [YYAvoidCrash errorMessageWithException:exception defaultToDo:AvoidCrashDefaultIgnore];
    }
    @finally {
        
    }
}

//                    insertObject:atIndex:
//=================================================================
#pragma mark - set方法
- (void)yy_avoidCrashInsertObject:(id)anObject atIndex:(NSUInteger)index {
    @try {
        [self yy_avoidCrashInsertObject:anObject atIndex:index];
    }
    @catch (NSException *exception) {
        [YYAvoidCrash errorMessageWithException:exception defaultToDo:AvoidCrashDefaultIgnore];
    }
    @finally {
        
    }
}


//=================================================================
//                           objectAtIndex:
//=================================================================
#pragma mark - objectAtIndex:

- (id)yy_avoidCrashObjectAtIndex:(NSUInteger)index {
    id object = nil;
    
    @try {
        object = [self yy_avoidCrashObjectAtIndex:index];
    }
    @catch (NSException *exception) {
        NSString *defaultToDo = AvoidCrashDefaultReturnNil;
        [YYAvoidCrash errorMessageWithException:exception defaultToDo:defaultToDo];
    }
    @finally {
        return object;
    }
}

//                     objectAtIndexedSubscript:
//=================================================================
#pragma mark - objectAtIndexedSubscript:
- (id)yy_avoidCrashObjectAtIndexedSubscript:(NSUInteger)idx {
    id object = nil;
    
    @try {
        object = [self yy_avoidCrashObjectAtIndexedSubscript:idx];
    }
    @catch (NSException *exception) {
        NSString *defaultToDo = AvoidCrashDefaultReturnNil;
        [YYAvoidCrash errorMessageWithException:exception defaultToDo:defaultToDo];
    }
    @finally {
        return object;
    }
    
}

//                         getObjects:range:
//=================================================================
#pragma mark - getObjects:range:
- (void)yy_avoidCrashGetObjects:(__unsafe_unretained id  _Nonnull *)objects range:(NSRange)range {
    
    @try {
        [self yy_avoidCrashGetObjects:objects range:range];
    } @catch (NSException *exception) {
        
        NSString *defaultToDo = AvoidCrashDefaultIgnore;
        [YYAvoidCrash errorMessageWithException:exception defaultToDo:defaultToDo];
        
    } @finally {
        
    }
}

@end
